package kbpost

import (
	"context"
	"strconv"
	"strings"

	"mall/common/globalkey"
	"mall/common/jwt"
	"mall/common/resultx"
	"mall/common/utils/pointy"
	"mall/service/forum/api/internal/svc"
	"mall/service/forum/api/internal/types"
	"mall/service/forum/api/internal/utils/parse"
	"mall/service/forum/rpc/forumclient"

	"github.com/zeromicro/go-zero/core/logx"
)

type GetEntryReviewLogic struct {
	logx.Logger
	ctx    context.Context
	svcCtx *svc.ServiceContext
}

func NewGetEntryReviewLogic(ctx context.Context, svcCtx *svc.ServiceContext) *GetEntryReviewLogic {
	return &GetEntryReviewLogic{
		Logger: logx.WithContext(ctx),
		ctx:    ctx,
		svcCtx: svcCtx,
	}
}

func (l *GetEntryReviewLogic) GetEntryReview(
	req *types.GetReviewListReq,
	headers *[]*types.Header,
) (resp *types.GetReviewListResp, err error) {
	if req.ParentId == nil || *req.ParentId == 0 {
		return nil, resultx.NewErrCode(resultx.FORUM_POST_PARENT_ID_REQUIRED)
	}

	userId := jwt.GetUserId(l.ctx)

	page, pageSize := parse.ParsePageInfo(
		req.Current,
		req.PageSize,
		l.svcCtx.Config.Query.DefaultAmount,
		l.svcCtx.Config.Query.MaxAmount,
	)

	preload := "forumPost:Id,Title,AuthorId,AuthorName,AuthorAvatar,AuthorRankId,AuthorRoleId,PublicDate,ContentHtml"
	eagerLoad := "forumPost:forumPostMeta,forumMedia"
	preload += ";forumPostMeta:mediaUrl"
	preload += ";forumMedia:Id,Uid,Uri,Url,Order,Thumbnail"

	var filters []string
	filters = append(filters, "ForumId,equalTo:"+strconv.FormatInt(l.svcCtx.Config.Query.PostForumId, 10))
	filters = append(filters, "ParentId,equalTo:"+strconv.FormatUint(*req.ParentId, 10))
	filters = append(filters, "Status,equalTo:"+strconv.FormatInt(int64(globalkey.StatusEnabled), 10))
	if req.Type == nil || *req.Type > 0 {
		filters = append(filters, "Sticky,equalTo:"+strconv.FormatInt(int64(*req.Type), 10))
	}
	platformId := globalkey.ThirdPartyPlatformWechatMini

	res, err := l.svcCtx.ForumRpc.GetPostList(l.ctx, &forumclient.BaseListReq{
		Offset:     uint32((page - 1) * pageSize),
		Limit:      uint32(pageSize),
		Preload:    pointy.GetPointer(preload),
		EagerLoad:  pointy.GetPointer(eagerLoad),
		Filter:     pointy.GetPointer(strings.Join(filters, ";")),
		VisitorId:  pointy.GetPointer(userId),
		PlatformId: pointy.GetPointer(platformId),
	})
	if err != nil {
		return nil, err
	}

	var hasNextPage bool
	var hasPreviousPage bool
	if res.HasNextPage != nil && *res.HasNextPage > 0 {
		hasNextPage = true
	}
	if res.HasPreviousPage != nil && *res.HasPreviousPage > 0 {
		hasPreviousPage = true
	}

	resp = &types.GetReviewListResp{
		BaseListInfo: types.BaseListInfo{
			HasNextPage:     hasNextPage,
			HasPreviousPage: hasPreviousPage,
		},
	}

	if len(res.List) > 0 {
		for _, v := range res.List {
			var mediaUrl *string
			if len(v.Meta) > 0 {
				for _, m := range v.Meta {
					if m.Key == nil || m.Value == nil {
						continue
					}

					val := *m.Value
					switch *m.Key {
					case "mediaUrl":
						mediaUrl = pointy.GetPointer(val)
					}
				}
			}

			var media []*types.TmpMediaInfo
			if len(v.Media) > 0 {
				for _, m := range v.Media {
					var url string
					if m.Url != nil && len(*m.Url) > 0 {
						url = *m.Url
					}
					if len(url) == 0 && m.Uri != nil && len(*m.Uri) > 0 {
						url = *m.Uri
					}

					media = append(media, &types.TmpMediaInfo{
						Uid:       m.Uid,
						Id:        m.Id,
						Thumbnail: m.Thumbnail,
						Order:     m.Order,
						Url:       pointy.GetPointer(url),
						AltText:   m.AltText,
					})
				}
			}

			resp.List = append(resp.List, &types.ReviewInfo{
				Id:             v.Id,
				Title:          v.PostTitle,
				ContentHtml:    v.PostContent,
				AuthorId:       v.AuthorId,
				AuthorNickname: v.AuthorNickname,
				AuthorAvatar:   v.AuthorAvatar,
				AuthorRankId:   v.AuthorRankId,
				AuthorRoleId:   v.AuthorRoleId,
				ImageUrl:       mediaUrl,
				PublicDate:     v.PublicDate,
				Media:          media,
			})
		}
	}

	return resp, nil

}
